package com.coocaa.ops.admin.v1.audit.service.impl;

import com.coocaa.ops.admin.async.log.service.LogRecordServiceImpl;
import com.coocaa.ops.admin.v1.audit.AuditUtil;
import com.coocaa.ops.admin.v1.audit.mapper.IAuditTaskInfoHistoryMapper;
import com.coocaa.ops.admin.v1.audit.mapper.IAuditTaskInfoMapper;
import com.coocaa.ops.admin.v1.audit.service.IAuditCommonService;
import com.coocaa.ops.admin.v1.audit.validator.AuditTaskValidator;
import com.coocaa.ops.common.core.base.mybatis.QueryTemplate;
import com.coocaa.ops.common.core.base.util.BeanCopyUtil;
import com.coocaa.ops.common.core.biz.audit.entity.AuditTaskInfoEntity;
import com.coocaa.ops.common.core.biz.audit.entity.AuditTaskInfoHistoryEntity;
import com.coocaa.ops.common.core.biz.auth.entity.SysUserEntity;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections4.CollectionUtils;
import org.springframework.beans.factory.InitializingBean;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.Date;
import java.util.List;

/**
 * @author bijiahao
 * @date : 2018/6/15.
 * @description: 审核相关的公共服务接口实现
 *
 */
@Slf4j
@Service
public class AuditCommonServiceImpl implements IAuditCommonService, InitializingBean{

    @Autowired
    private IAuditTaskInfoMapper auditTaskInfoMapper;
    @Autowired
    private IAuditTaskInfoHistoryMapper auditTaskInfoHistoryMapper;
    @Autowired
    private LogRecordServiceImpl logRecordService;

    @Override
    public void afterPropertiesSet() throws Exception {
        AuditUtil.setAuditCommonService(this);
    }

    /**
     * 打开任务
     * @param entity
     * @param user
     * @return
     */
    @Override
    public AuditTaskInfoEntity openTask(AuditTaskInfoEntity entity, SysUserEntity user) {
        long startTime = System.currentTimeMillis();
        AuditTaskInfoEntity taskInfo = this.getTaskByIdAndVersionAndType(entity.getResourceId(), entity.getResourceVersion(), entity.getResourceType());
        if (taskInfo == null) {
            taskInfo = new AuditTaskInfoEntity();
            taskInfo.setCurrentOperator(user.getId());
        } else {
            //清空当前认领人和审核意见
            taskInfo.setCurrentOperator(0);
            taskInfo.setAuditDesc("");
        }
        taskInfo.setTaskName(entity.getTaskName());
        taskInfo.setResourceId(entity.getResourceId());
        taskInfo.setResourceVersion(entity.getResourceVersion() == null ? -1 : entity.getResourceVersion());
        taskInfo.setResourceType(entity.getResourceType());
        taskInfo.setSource(entity.getSource() == null ? "" : entity.getSource());
        taskInfo.setCreator(user.getId());
        taskInfo.setPriority(entity.getPriority() == null ? Integer.valueOf(1) : entity.getPriority());
        taskInfo.setTaskFlag(1);
        taskInfo.setAuditFlag(3);
        taskInfo.setLastUpdateDate(new Date());
        taskInfo.setCreatedDate(new Date());
        taskInfo.setFlag(1);
        Integer taskId = taskInfo.getTaskId();
        if (taskId == null) {
            auditTaskInfoMapper.insert(taskInfo);
        } else {
            this.updateById(taskInfo);
        }
        long endTime = System.currentTimeMillis();
        logRecordService.logOpRecord(taskInfo, endTime - startTime, user);
        return taskInfo;
    }

    /**
     * 更新任务信息
     *
     * @param entity
     */
    @Override
    public void updateById(AuditTaskInfoEntity entity) {
        entity.setLastUpdateDate(new Date());
        auditTaskInfoMapper.updateById(entity);
    }

    /**
     * 保存任务历史信息
     *
     * @param entity
     */
    @Override
    public void saveAuditTaskInfoHistory(AuditTaskInfoEntity entity) {
        AuditTaskInfoHistoryEntity historyEntity = new AuditTaskInfoHistoryEntity();
        BeanCopyUtil.copyOrig2Target(entity, historyEntity, "审核任务实体类复制");
        auditTaskInfoHistoryMapper.insert(historyEntity);
    }

    /**
     * 获取任务信息-通过资源ID-版本-类别
     *
     * @param resourceId
     * @param resourceVersion
     * @param resourceType
     * @return
     */
    @Override
    public AuditTaskInfoEntity getTaskByIdAndVersionAndType(Integer resourceId, Integer resourceVersion, String resourceType) {
        QueryTemplate<AuditTaskInfoEntity> wrapper = this.getEntityWrapperForAuditTask(resourceId, resourceVersion, resourceType);
        wrapper.orderByDesc("last_update_date");
        wrapper.last("limit 1");
        List<AuditTaskInfoEntity> auditTaskInfoList = auditTaskInfoMapper.selectList(wrapper);
        if (CollectionUtils.isNotEmpty(auditTaskInfoList)) {
            return auditTaskInfoList.get(0);
        }
        return null;
    }

    /**
     * 查询审核任务历史信息-通过资源ID-版本-类别
     *
     * @param resourceId
     * @param version
     * @param resourceType
     * @return
     */
    @Override
    public List<AuditTaskInfoHistoryEntity> queryAuditHistory(Integer resourceId, Integer version, String resourceType) {
        QueryTemplate<AuditTaskInfoHistoryEntity> wrapper = QueryTemplate.getEqQueryTemplate("flag", 1);
        wrapper.eq("resource_id", resourceId)
                .eq("resource_type", resourceType);
        if (AuditTaskValidator.isVersionCanUseForQueryParam(version)) {
            wrapper.eq("resource_version", version);
        }
        wrapper.orderByDesc("last_update_date");
        List<AuditTaskInfoHistoryEntity> list = auditTaskInfoHistoryMapper.selectList(wrapper);
        return list;
    }

    /**
     * 删除任务信息-通过资源ID-版本-类别
     *
     * @param id
     * @param version
     * @param type
     */
    @Override
    public void logicDelByIdAndVersionAndType(Integer id, Integer version, String type) {
        QueryTemplate<AuditTaskInfoEntity> wrapper = this.getEntityWrapperForAuditTask(id, version, type);
        AuditTaskInfoEntity update = new AuditTaskInfoEntity();
        update.setFlag(0);
        auditTaskInfoMapper.update(update, wrapper);
    }

    /**
     * 封装查询条件-通过资源ID-版本-类别
     *
     * @param resourceId
     * @param resourceVersion
     * @param resourceType
     * @return
     */
    private QueryTemplate<AuditTaskInfoEntity> getEntityWrapperForAuditTask(Integer resourceId, Integer resourceVersion, String resourceType) {
        QueryTemplate<AuditTaskInfoEntity> wrapper = QueryTemplate.getEqQueryTemplate("flag", 1);
        wrapper.eq("resource_id", resourceId)
                .eq("resource_type", resourceType);
        if (AuditTaskValidator.isVersionCanUseForQueryParam(resourceVersion)) {
            wrapper.eq("resource_version", resourceVersion);
        }
        return wrapper;
    }


}
